package com.zy.explore.rocketmq.domain.mongo.entity;

import com.zy.explore.rocketmq.interfaces.frm.SortFieldFrm;
import com.zy.explore.rocketmq.interfaces.frm.ExampleQueryFrm;
import cn.hutool.core.date.DateUtil;
import com.google.common.collect.Lists;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.springframework.data.domain.Sort;
import org.springframework.data.mongodb.core.mapping.Document;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;

import java.util.Date;
import java.util.List;

/**
 * description 示例Mongo实体类
 *
 * @author ZY
 * @date 2021年05月19日 00:13
 */
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
@Document(collection = "com.zy.explore.user")
public class MongoExampleEntity {

    private String id;

    private String name;

    private String address;

    private Date createTime;

    private Date updateTime;

    /**
     * Frm 转 Query
     *
     * @param frm 参数对象
     * @return 返回Query对象
     */
    public static Query convertToQuery(ExampleQueryFrm frm) {
        if (frm.getPageNum() == null || frm.getPageNum() <= 0) {
            frm.setPageNum(1);
        }
        if (frm.getPageSize() == null || frm.getPageSize() <= 0) {
            frm.setPageSize(10);
        }
        Query query = new Query();

        if (frm.getId() != null) {
            query.addCriteria(Criteria.where("id").is(frm.getId()));
        }
        if (!StringUtils.isEmpty(frm.getName())) {
            query.addCriteria(Criteria.where("name").regex("^.*" + frm.getName() + ".*$"));
        }
        if (!StringUtils.isEmpty(frm.getAddress())) {
            query.addCriteria(Criteria.where("address").regex("^.*" + frm.getAddress() + ".*$"));
        }
        if (!StringUtils.isEmpty(frm.getCreateTimeBegin()) && StringUtils.isEmpty(frm.getCreateTimeEnd())) {
            query.addCriteria(Criteria.where("createTime").gte(DateUtil.parse(frm.getCreateTimeBegin(), "yyyy-MM-dd")));
        }
        if (!StringUtils.isEmpty(frm.getCreateTimeEnd()) && StringUtils.isEmpty(frm.getCreateTimeBegin())) {
            query.addCriteria(Criteria.where("createTime").lte(DateUtil.parse(frm.getCreateTimeEnd(), "yyyy-MM-dd")));
        }
        if (!StringUtils.isEmpty(frm.getCreateTimeBegin()) && !StringUtils.isEmpty(frm.getCreateTimeEnd())) {
            query.addCriteria(Criteria.where("createTime").gte(DateUtil.parse(frm.getCreateTimeBegin(), "yyyy-MM-dd"))
                    .lte(DateUtil.parse(frm.getCreateTimeEnd(), "yyyy-MM-dd")));
        }
        if (!StringUtils.isEmpty(frm.getUpdateTimeBegin()) && StringUtils.isEmpty(frm.getUpdateTimeEnd())) {
            query.addCriteria(Criteria.where("updateTime").gte(DateUtil.parse(frm.getUpdateTimeBegin(), "yyyy-MM-dd")));
        }
        if (!StringUtils.isEmpty(frm.getUpdateTimeEnd()) && StringUtils.isEmpty(frm.getUpdateTimeBegin())) {
            query.addCriteria(Criteria.where("updateTime").lte(DateUtil.parse(frm.getUpdateTimeEnd(), "yyyy-MM-dd")));
        }
        if (!StringUtils.isEmpty(frm.getUpdateTimeBegin()) && !StringUtils.isEmpty(frm.getUpdateTimeEnd())) {
            query.addCriteria(Criteria.where("updateTime").gte(DateUtil.parse(frm.getUpdateTimeBegin(), "yyyy-MM-dd"))
                    .lte(DateUtil.parse(frm.getUpdateTimeEnd(), "yyyy-MM-dd")));
        }
        // 排序
        List<SortFieldFrm> sortFields = frm.getSortFields();
        List<Sort.Order> orders = Lists.newArrayList();
        if (!CollectionUtils.isEmpty(sortFields)) {
            sortFields.forEach(sortField -> {
                if (Sort.Direction.ASC.name().equalsIgnoreCase(sortField.getOrder())) {
                    orders.add(new Sort.Order(Sort.Direction.ASC, sortField.getPropName()));
                } else if (Sort.Direction.DESC.name().equalsIgnoreCase(sortField.getOrder())) {
                    orders.add(new Sort.Order(Sort.Direction.DESC, sortField.getPropName()));
                }
            });
        } else {
            // 默认按主键降序排序
            orders.add(new Sort.Order(Sort.Direction.DESC, "id"));
        }
        return query.with(Sort.by(orders));
    }
}